﻿#include "chatdialog.h"
#include "ui_chatdialog.h"
#include <QtDebug>

ChatDialog::ChatDialog(QString in_name, int in_ID, int in_grep, QWidget *parent)
    : QDialog(parent)
    , ui(new Ui::ChatDialog)
{
     name = in_name;
     ID = in_ID;
     grep = in_grep;

    ui->setupUi(this);

    ui->textMsg->setFocus();

    connect(&sock, &QTcpSocket::connected, this, &ChatDialog::connectedToServer);
    connect(&sock, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(error(QAbstractSocket::SocketError)));

    sock.connectToHost("192.168.0.35", 2000);

    qDebug() << sock.state();


    ui->textRecord->moveCursor(QTextCursor::End);

    date dat;

    dat.grep_id = grep;
    dat.sleek = 0;
    dat.file_type = ADDGREP;
    dat.size = ID;            //自己的ID
    strcpy( dat.talk, name.toStdString().c_str());

    sock.write((const char *)&dat, qint64(sizeof(dat)));
    sock.read((char *)&dat, qint64(sizeof(dat)));


#if(1)


    // 创建新的 QTcpServer 对象
    sock_listen = new QTcpServer(this);

    QHostAddress localAddress = sock.localAddress();
    quint16 localPort = sock.localPort();

    sock.close();

    if (sock_listen->listen(localAddress, localPort))
    {
        qDebug() << "Client listening on " << localAddress << ":" << localPort;

        // 当有新连接时，连接到新连接的槽函数
        connect(sock_listen, &QTcpServer::newConnection, this, &ChatDialog::newConnection);
    }
    else
    {
        qDebug() << "Failed to start client listener.";
    }

#endif

}

void ChatDialog::newConnection()
{
    QTcpSocket *newClientSocket = sock_listen->nextPendingConnection();

    if (newClientSocket)
    {
        qDebug() << "New connection from " << newClientSocket->peerAddress() << ":" << newClientSocket->peerPort();

        // 连接新连接的信号和槽，以处理新连接的消息
        connect(newClientSocket, &QTcpSocket::readyRead, this, &ChatDialog::recvMsg);
    }
}
ChatDialog::~ChatDialog()
{
    delete sock_listen;
    delete ui;
    delete this;
}


void ChatDialog::on_btnSendMsg_clicked()
{

    QString msg = ui->textMsg->toPlainText();

    size_t sleek = 0;
    size_t Size = msg.size();
   const char *buf = msg.toStdString().c_str();
   date dat;

   dat.file_type = CHAT;

   dat.size = ID;
   dat.grep_id = grep;
   dat.sleek = Size;    //sleek是文件大小

   strcpy(dat.talk, name.toStdString().c_str());


   connect(&sock, &QTcpSocket::connected, this, &ChatDialog::connectedToServer);
   connect(&sock, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(error(QAbstractSocket::SocketError)));


   sock.connectToHost("192.168.0.35", 2000);
   sock.write((char * )&dat, qint64(sizeof(dat)));

   while (sleek  < Size)
   {
       dat.sleek = sleek;

       dat.size = ((Size - sleek) >= _DATAPAEK) ? _DATAPAEK : Size - sleek;

       memcpy(dat.talk, buf + sleek, qint64(dat.size));

       sock.write((char * )&dat, qint64(sizeof(dat)));
       sleek  += _DATAPAEK;

   }

    dat.file_type = SENDOUT;
    sock.write((char * )&dat, qint64(sizeof(dat)));//发送挥手包，表示数据传输完毕

    sock.close();

    QByteArray msgData = msg.toUtf8() + '\0';

    ui->textRecord->appendPlainText(QString("\n%1\n").arg(msg));
    ui->textRecord->moveCursor(QTextCursor::End);

    ui->textMsg->clear();
    ui->textMsg->setFocus();
}

void ChatDialog::connectedToServer()
{
    qDebug() << "connected!";

//    ui->textRecord->appendPlainText("\n连接服务器成功！\n");
    ui->textRecord->moveCursor(QTextCursor::End);
//    ui->btnSendMsg->setEnabled(true);
}

void ChatDialog::recvMsg()
{
    QTcpSocket *clientSocket = qobject_cast<QTcpSocket*>(sender());
    if (!clientSocket)
        return;


    QByteArray msg;
    date dat = {0, 0, 0, 0,""};


    sock.read((char *)&dat, qint64(sizeof (dat)));

    if(dat.file_type == HEARTBEAT)
    {
        sock.write((const char *)&dat, qint64(sizeof(dat)));
        return;
    }

    ui->textRecord->appendPlainText(dat.talk);
    ui->textRecord->appendPlainText(QString::number(dat.size));

    if(dat.sleek > 1000000)
    {
        return;
    }

    char *buf = new char[dat.sleek]();

    while(sock.read((char *)&dat, qint64(sizeof (dat))) != -1)
    {
        if(dat.file_type == SENDOUT)
        {
            break;
        }

        memcpy(buf, dat.talk, dat.size);
    }
    qDebug() << buf << endl;

    ui->textRecord->appendPlainText(buf);
    ui->textRecord->appendPlainText("\n");

}

void ChatDialog::error(QAbstractSocket::SocketError socketError)
{
    qDebug() << "error!" << socketError << sock.state();

    if(sock.state() == QAbstractSocket::UnconnectedState)
    {
        ui->textRecord->appendPlainText("\n连接服务器失败，请检查网络连接！\n");
        ui->textRecord->moveCursor(QTextCursor::End);

        sock.connectToHost("192.168.0.35", 2000);

        ui->textRecord->appendPlainText("\n正在尝试重新连接服务器 ...\n");
        ui->textRecord->moveCursor(QTextCursor::End);
    }
}
